﻿using Pay.Core;
using Pay.Data;
using Pay.DTO;
using Pay.IService;
using Pay.Service.Cache;
using Pay.TO;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace Pay.Service {
    public class ProductTokenMakerService : ServiceBase, IProductTokenMakerService, IDisposable {
        private IUnitOfWork _iUnitOfWork;
        private IProductService _iProductService;
        public ProductTokenMakerService(IUnitOfWork iUnitOfWork, IProductService iProductService) : base(iUnitOfWork) {
            _iUnitOfWork = iUnitOfWork;
            _iProductService = iProductService;
        }

        /// <summary>
        /// 获得创客商品列表
        /// </summary>
        /// <param name="query"></param>
        /// <returns></returns>
        public PagedResult<product_token_maker_dto_ex> GetProductTokenMakers(ProductTokenMakerQuery query) {
            var filter = PredicateBuilder.True<ProductTokenMaker>();
            if (!string.IsNullOrEmpty(query.product_name)) {
                filter = filter.And(c => c.ProductActivity.Product.Name.Contains(query.product_name));
            }
            var result = context.ProductTokenMaker.FromCachePaged<ProductTokenMaker, product_token_maker_dto_ex>(query.page, query.size, filter, orderBy => orderBy.OrderByDescending(o => o.ProductActivity.Product.Top).ThenByDescending(o => o.ProductActivity.Top));
            return result;
        }

        /// <summary>
        /// 获得创客商品
        /// </summary>
        /// <param name="product_activity_id"></param>
        /// <returns></returns>
        public product_token_maker_dto_ex GetProductTokenMaker(long product_activity_id) {
            return context.ProductTokenMaker.Where(o => o.ProductActivityId == product_activity_id).FirstOrDefault().ToDtoObject<product_token_maker_dto_ex>();
        }

        /// <summary>
        /// 获得创客商品
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public product_token_maker_dto_ex GetByProductId(long product_id) {
            return context.ProductTokenMaker.FirstOrDefault(o => o.ProductActivity.ProductId == product_id).ToDtoObject<product_token_maker_dto_ex>();
        }

        /// <summary>
        /// 获取创客商品
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public product_token_maker_edit_dto GetForEdit(long id) {
            var dto = GetProductTokenMaker(id);
            var result = new product_token_maker_edit_dto();
            dto.ToCopyProperty(result);
            result.top = dto.product_activity.top;
            result.price = dto.product_activity.activity_price;
            result.cost_price = (decimal)dto.cost_price;
            result.distribution_price = dto.distribution_price;
            result.status_value = (dto.product_activity.product.audit_status == AuditStatus.Sell && dto.product_activity.product.sale_status == SaleStatus.Sell) ? "1" : "2";
            return result;
        }

        /// <summary>
        /// 新增创客商品
        /// </summary>
        /// <param name="productId"></param>
        /// <returns></returns>
        public int AddProductTokenMaker(long productId) {
            if (context.ProductActivity.Exist(o => o.ProductId == productId && o.Activity.Type == EActivityType.ProductMaker))
                throw new ServerErrorException("该商品已存在该活动中");
            DateTime timeNow = DateTime.Now;
            if (context.ProductActivity.Exist(o => o.ProductId == productId && o.Activity.Type != EActivityType.ProductMaker && o.Activity.EndTime >= timeNow))
                throw new ServerErrorException("该商品已存在其他活动中");
            var activity = context.Activity.Where(o => o.Type == EActivityType.ProductMaker).FirstOrDefault();
            if (activity == null)
                throw new ServerErrorException("请先创建创客导购类型活动");
            var product = context.Products.FindById(productId);
            List<ProductSku> productSkuList = product.ProductSkus.ToList();
            List<string> cacheTags = new List<string>();
            if (productSkuList == null || productSkuList.Count() == 0) {//无规格
                productSkuList = new List<ProductSku>() { new ProductSku() { Id = 0, ProductId = product.Id, Stock = product.Stock, Price = product.Price, CostPrice = product.CostPrice ?? 0, DistributionPrice = product.DistributionPrice ?? 0} };
            }
            using (var trans = context.Database.BeginTransaction()) {
                try {
                    foreach (var sku in productSkuList) {
                        var productActivity = new ProductActivity() {
                            ActivityId = activity.Id,
                            ProductId = productId,
                            ProductSkuId = sku.Id,
                            ActivityPrice = sku.Price,
                            ActivityStock = sku.Stock,
                            CreateTime = DateTime.Now.ToUnix()
                        };
                        context.ProductActivity.Add(productActivity);
                        _iUnitOfWork.Commit();
                        var productTokenMaker = new ProductTokenMaker() { ProductId = productId, ProductActivityId = productActivity.Id, CostPrice = sku.CostPrice, DistributionPrice = sku.DistributionPrice };
                        context.ProductTokenMaker.Add(productTokenMaker);
                        product.SaleStatus = SaleStatus.OutOfStock;
                    }

                    cacheTags = new List<string>() { "Product", "Product" + productId, "DistributionProduct" };
                    //更新分销表
                    List<DistributionProduct> distributionProducts = context.DistributionProducts.Where(o => o.ProductId == productId).ToList();
                    if (distributionProducts != null) {
                        foreach (var dp in distributionProducts) {
                            dp.Status = EDistributionProductStatus.Deleted;
                            cacheTags.Add("DistributionProduct" + dp.MerchantId);
                        }
                    }

                    int result = _iUnitOfWork.Commit(cacheTags.ToArray());
                    trans.Commit();
                    return result;
                }
                catch (ServerErrorException ex) {
                    trans.Rollback();
                    throw ex;
                }
                catch (Exception ex) {
                    trans.Rollback();
                    throw ex;
                }
            }
        }

        /// <summary>
        /// 更新创客商品
        /// </summary>
        /// <param name="dto"></param>
        /// <returns></returns>
        public int UpdateProductTokenMaker(product_token_maker_edit_dto dto) {
            if (dto.cost_price > dto.price)
                throw new ServerErrorException("结算价不能大于销售价");
            if ((dto.first_rate + dto.second_rate + dto.node_mall_rate + dto.county_agent_rate + dto.city_agent_rate) > 1)
                throw new ServerErrorException("一级、二级、节点商城、超级节点、市分公司 比例之和不能大于1");
            if (dto.distribution_rate < 0 || dto.distribution_rate > 1)
                throw new ServerErrorException("分销比例必须在0-1之间");
            var marketProduct = context.ProductTokenMaker.Where(o => o.ProductActivityId == dto.product_activity_id).FirstOrDefault();
            var productActivityList = context.ProductActivity.Where(o => o.ProductId == marketProduct.ProductActivity.ProductId && o.ActivityId == marketProduct.ProductActivity.ActivityId).ToList();
            var product = context.Products.FindById(marketProduct.ProductActivity.ProductId);
            marketProduct.FirstRate = dto.first_rate;
            marketProduct.SecondRate = dto.second_rate;
            marketProduct.NodeMallRate = dto.node_mall_rate;
            marketProduct.CountyAgentRate = dto.county_agent_rate;
            marketProduct.CityAgentRate = dto.city_agent_rate;

            marketProduct.ProductActivity.ActivityPrice = dto.price;
            marketProduct.CostPrice = dto.cost_price;
            marketProduct.DistributionPrice = (dto.price - dto.cost_price) * dto.distribution_rate;
            marketProduct.ProductActivity.Top = dto.top;
            productActivityList.ForEach(o => { o.Top = dto.top; });
            if (dto.status_value == "2")
                product.SaleStatus = SaleStatus.OutOfStock;
            else if (dto.status_value == "1") {
                if (product.Stock <= 0)
                    throw new ServerErrorException("库存不足无法上架");

                product.AuditStatus = AuditStatus.Sell;
                product.SaleStatus = SaleStatus.Sell;
            }

            List<string> cacheList = new List<string>() {"Product", "Product" + marketProduct.ProductActivity.ProductId };
            foreach (var pa in productActivityList) {
                cacheList.Add("ProductTokenMaker" + pa.ProductTokenMaker.ProductActivityId);
                cacheList.Add("productActivity" + pa.ProductTokenMaker.ProductActivityId);
                cacheList.Add("ProductActivity" + pa.ProductId + "_" + pa.ProductSkuId);
                cacheList.Add("ProductActivity" + pa.ProductId);
            }

            int result = _iUnitOfWork.Commit(cacheList.ToArray());
            return result;
        }

        /// <summary>
        /// 删除创客商品
        /// </summary>
        /// <param name="product_activity_id"></param>
        /// <returns></returns>
        public int DeleteProductTokenMaker(long product_activity_id) {
            List<string> cacheList = new List<string>();
            var marketProduct = context.ProductTokenMaker.Where(o => o.ProductActivityId == product_activity_id).FirstOrDefault();
            var productActivityList = context.ProductActivity.Where(o => o.ProductId == marketProduct.ProductActivity.ProductId && o.ActivityId == marketProduct.ProductActivity.ActivityId).ToList();
            var marketProductList = productActivityList.Select(o => o.ProductTokenMaker).ToList();
            foreach (var pa in productActivityList) {
                cacheList.Add("ProductTokenMaker" + pa.ProductTokenMaker.ProductActivityId);
                cacheList.Add("productActivity" + pa.ProductTokenMaker.ProductActivityId);
                cacheList.Add("ProductActivity" + pa.ProductId + "_" + pa.ProductSkuId);
                cacheList.Add("ProductActivity" + pa.ProductId);
            }
            context.ProductTokenMaker.RemoveRange(marketProductList);
            context.ProductActivity.RemoveRange(productActivityList);
            int result = _iUnitOfWork.Commit(cacheList.ToArray());
            return result;
        }


    }
}
